package com.msb.c10;

import sun.plugin2.util.SystemUtil;

import java.util.concurrent.atomic.AtomicLong;
import java.util.concurrent.atomic.LongAdder;

/**
 * @author: xw
 * @create: 2022/10/3 13:19
 * @description:
 */
public class Code02_AtomicVsSynchronized {
    volatile static long count2 = 0L;
    static AtomicLong count1 = new AtomicLong(0L);
    static LongAdder count3 = new LongAdder();

    public static void main(String[] args) throws InterruptedException {
        Thread[] threads = new Thread[1000];
//1283
//        for (int i = 0; i < 1000; i++) {
//            threads[i] = new Thread(new Runnable() {
//                @Override
//                public void run() {
//                    for(int k=0; k<100000; k++) {
//                        count1.incrementAndGet();
//                    }
//                }
//            });
//        }
        for (int i = 0; i < 1000; i++) {
            threads[i] = new Thread(()->{
                for(int k=0; k<100000; k++) {
                    count1.incrementAndGet();
                }
            });
        }
        long start = System.currentTimeMillis();
        for(Thread t : threads ) {
            t.start();
        }

        for (Thread t : threads) {
                t.join();
        }
        long end = System.currentTimeMillis();

        System.out.println("Atomic: " + count1.get() + " time " + (end-start));

        Object lock = new Object();
        for(int i=0; i<threads.length; i++) {
//            2512
//            threads[i] =
//                    new Thread(new Runnable() {
//                        @Override
//                        public void run() {
//                            for (int k = 0; k < 100000; k++)
//                                synchronized (lock) {
//                                    count2++;
//                                }
//                        }
//                    });
            threads[i] = new Thread(() -> {
                for (int k = 0; k < 100000; k++) {
                    synchronized (lock) {
                        count2++;
                    }
                }
            });
        }
        start = System.currentTimeMillis();

        for(Thread t : threads ) t.start();

        for (Thread t : threads) t.join();

        end = System.currentTimeMillis();


        System.out.println("Sync: " + count2 + " time " + (end-start));

        for(int i=0; i<threads.length; i++) {
            threads[i] =
                    new Thread(()-> {
                        for(int k=0; k<100000; k++) count3.increment();
                    });
        }

        start = System.currentTimeMillis();

        for(Thread t : threads ) t.start();

        for (Thread t : threads) t.join();

        end = System.currentTimeMillis();

        //TimeUnit.SECONDS.sleep(10);

        System.out.println("LongAdder: " + count1.longValue() + " time " + (end-start));
    }
}
